package com.gcb.framework.service.impl;


import com.gcb.common.core.domain.entity.SysDept;
import com.gcb.common.core.domain.entity.SysUser;
import com.gcb.common.exception.ServiceException;
import com.gcb.framework.mapper.SysUsersMapper;
import com.gcb.framework.service.IOperateManageService;
import com.gcb.framework.service.ISysConfigService;
import com.gcb.framework.service.ISysDeptService;
import com.gcb.framework.service.ISysRoleService;
import com.gcb.framework.service.ISysUserService;
import com.gcb.framework.utils.SecurityUtils;
import com.gcb.common.utils.StringUtils;
import com.gcb.common.utils.bean.BeanUtils;
import com.gcb.framework.domain.dto.OperateInsertDto;
import com.gcb.framework.domain.dto.OperateSearchDto;
import com.gcb.framework.domain.export.OperateExport;
import com.gcb.framework.domain.vo.UserDeptVo;
import com.gcb.framework.mapper.SysDeptMapper;
import com.gcb.framework.mapper.SysUserRoleMapper;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;

import static com.gcb.common.enums.DeptType.OPERATE;
import static com.gcb.framework.utils.SecurityUtils.getDeptIds;


/**
 * 运营管理 服务实现
 *
 * @author jy
 */
@Service
public class OperateManageServiceImpl implements IOperateManageService {
    @Autowired
    private SysDeptMapper deptMapper;
    @Autowired
    private ISysUserService userService;
    @Autowired
    private ISysConfigService configService;
    @Autowired
    private SysUsersMapper userMapper;
    @Autowired
    private ISysRoleService roleService;
    @Autowired
    private SysUserRoleMapper sysUserRoleMapper;
    @Autowired
    private ISysDeptService sysDeptService;


    /**
     * 查询运营管理数据
     *
     * @param dept 运营信息
     * @return 运营信息集合
     */
    @Override
    public List<SysDept> selectOperatetList(SysDept dept) {
        List<SysDept> sysDepts = deptMapper.selectDeptList(dept);
        for (SysDept sysDept : sysDepts) {
            //查询子运营超级管理员
            SysUser sysUser = userMapper.selectOperateAreaAdmin(sysDept.getDeptId());
            if (sysUser != null) {
                sysDept.setAdminUser(sysUser.getUserName());
                sysDept.setPhonenumber(sysUser.getPhonenumber().replaceAll("(\\d{3})\\d{4}(\\d{4})", "$1****$2"));
            }
        }
        return sysDepts;
    }

    @Override
    public List<OperateExport> selectOperatetExportList(SysDept dept) {
        List<SysDept> sysDepts = deptMapper.selectDeptList(dept);
        if (!sysDepts.isEmpty()) {
            List<OperateExport> exportList = sysDepts.stream().map(operate -> {
                OperateExport export = new OperateExport();
                BeanUtils.copyProperties(operate, export);
                //查询子运营超级管理员
                SysUser sysUser = userMapper.selectOperateAreaAdmin(operate.getDeptId());
                export.setAdminUser(sysUser.getUserName());
                export.setPhonenumber(sysUser.getPhonenumber().replaceAll("(\\d{3})\\d{4}(\\d{4})", "$1****$2"));
                return export;
            }).collect(Collectors.toList());
            return exportList;
        }
        return null;
    }

    /**
     * 新增保存运营信息
     *
     * @param dept 运营信息
     * @return 结果
     */
    @Override
    @Transactional
    public int insertOperate(OperateInsertDto dept) {
        SysDept info = deptMapper.selectDeptById(dept.getParentId());
        dept.setAncestors(info.getAncestors() + "," + dept.getParentId());
        //运营商公司名称 不能重复
        List<SysDept> byName = deptMapper.selectDeptList(new OperateSearchDto() {{
            setDeptName(dept.getDeptName());
        }});
        if (!byName.isEmpty()) {
            throw new ServiceException("运营商公司名称重复，请重新填写");
        }
        //新增运营
        SysDept sysDept = new SysDept();
        BeanUtils.copyProperties(dept, sysDept);
        sysDept.setDeptType(OPERATE.getCode());
        deptMapper.insertDept(sysDept);
        //新增对应超级管理员
        SysUser user = new SysUser();
        user.setUserName(dept.getUserName());
        user.setNickName(dept.getUserName());
        user.setPhonenumber(dept.getPhonenumber());
        user.setDeptId(sysDept.getDeptId());
//        String password = configService.selectConfigByKey("sys.user.initPassword");
        user.setPassword(SecurityUtils.encryptPassword(user.getPhonenumber().substring(user.getPhonenumber().length() - 6)));
        //配置运营超级管理员角色
        user.setRoleIds(new Long[]{100L});
        if (StringUtils.isNotEmpty(user.getPhonenumber()) && !userService.checkPhoneUnique(user)) {
            SysUser sysUser = userMapper.checkPhoneUnique(user.getPhonenumber());
            //如果用户以存在直接在用户角色关系表中新增记录 支持多部门切换
            user.setUserId(sysUser.getUserId());
            userService.insertUserRole(user);
        } else {
            userService.insertUser(user);
        }
        //为子运营生成两个默认角色 普通用户  管理员
        roleService.generateAcquiesceRole(sysDept);

        return 1;
    }

    /**
     * 根据运营ID查询信息
     *
     * @param deptId 部门ID
     * @return 运营信息
     */
    @Override
    public SysDept selectOperateById(Long deptId) {
        SysDept sysDept = deptMapper.selectDeptById(deptId);
        //查询子运营超级管理员
        SysUser sysUser = userMapper.selectOperateAreaAdmin(sysDept.getDeptId());
        sysDept.setAdminUser(sysUser.getUserName());
        sysDept.setPhonenumber(sysUser.getPhonenumber());
        return sysDept;
    }

    /**
     * 修改保存运营信息
     *
     * @param dept 运营信息
     * @return 结果
     */
    @Override
    public int updateOperate(OperateInsertDto dept) {
        //运营商公司名称 不能重复
        List<SysDept> byName = deptMapper.selectDeptList(new OperateSearchDto() {{
            setDeptName(dept.getDeptName());
        }});

        SysDept newParentDept = deptMapper.selectDeptById(dept.getParentId());
        SysDept oldDept = deptMapper.selectDeptById(dept.getDeptId());
        if (StringUtils.isNotNull(newParentDept) && StringUtils.isNotNull(oldDept)) {
            String newAncestors = newParentDept.getAncestors() + "," + newParentDept.getDeptId();
            String oldAncestors = oldDept.getAncestors();
            dept.setAncestors(newAncestors);
            updateDeptChildren(dept.getDeptId(), newAncestors, oldAncestors);
        }
        return deptMapper.updateDept(dept);
    }

    /**
     * 更新运营信息
     *
     * @param dept 运营信息
     */
    @Override
    public int updateOperateStatus(OperateInsertDto dept) {
        //如果是禁用运营商 查询当前是该部门的可登录用户 如果该用户有多个未禁用的部门 则自动切换随机一个
        if (dept.getStatus().equals("1")) {
            List<SysUser> sysUsers = userMapper.selectOperateUserList(getDeptIds(sysDeptService.selectDeptTreeList(new SysDept()), new ArrayList<>()));
            for (SysUser sysUser : sysUsers) {
                List<UserDeptVo> userDeptList = sysUserRoleMapper.getUserDeptList(sysUser.getUserId());
                if (!userDeptList.isEmpty()) {
                    sysUser.setDeptId(userDeptList.get(0).getDeptId());
                    userMapper.updateUser(sysUser);
                }
            }
        }
        return deptMapper.updateDept(dept);
    }

    /**
     * 根据条件分页查询运营账号用户列表
     *
     * @param user 用户信息
     * @return 用户信息集合信息
     */
    @Override
    public List<SysUser> operateUserList(SysUser user) {
        List<SysUser> sysUsers = userMapper.operateUserList(user);
        sysUsers.forEach(e -> {
            if (StringUtils.isNotBlank(e.getPhonenumber()) && e.getPhonenumber().length() == 11) {
                e.setPhonenumber(e.getPhonenumber().replaceAll("(\\d{3})\\d{4}(\\d{4})", "$1****$2"));
            }
        });
        return sysUsers;
    }


    /**
     * 修改子元素关系
     *
     * @param deptId       被修改的部门ID
     * @param newAncestors 新的父ID集合
     * @param oldAncestors 旧的父ID集合
     */
    public void updateDeptChildren(Long deptId, String newAncestors, String oldAncestors) {
        List<SysDept> children = deptMapper.selectChildrenDeptById(deptId);
        for (SysDept child : children) {
            child.setAncestors(child.getAncestors().replaceFirst(oldAncestors, newAncestors));
        }
        if (children.size() > 0) {
            deptMapper.updateDeptChildren(children);
        }
    }

}
